// src/hooks/useTable.ts
import { ref, reactive, unref, onMounted } from 'vue';

export interface UseTableOptions<TQuery = any, TResult = any> {
  /** 请求接口方法，返回 Promise */
  api: (params: TQuery) => Promise<any>;
  /** 默认查询参数 */
  defaultQuery?: Partial<TQuery>;
  /** 是否立即请求 */
  immediate?: boolean;
  /** 是否需要分页 */
  pagination?: boolean;
}

export function useTable<TQuery extends Record<string, any> = any, TResult = any>(
  options: UseTableOptions<TQuery, TResult>,
) {
  const { api, defaultQuery, immediate = true, pagination = true } = options;

  const loading = ref(false);
  const tableData = ref<TResult[]>([]);
  const total = ref(0);

  /** 组装 query 参数 */
  const baseQuery = pagination
    ? { pageNum: 1, pageSize: 10, ...(defaultQuery || {}) }
    : { ...(defaultQuery || {}) };

  const query = reactive(baseQuery) as TQuery & { pageNum?: number; pageSize?: number };

  /** 核心请求方法 */
  const loadData = async () => {
    try {
      loading.value = true;

      const params = unref(query);

      // 如果没有分页，不传 pageNum、pageSize
      const realParams = pagination
        ? params
        : { ...params, pageNum: undefined, pageSize: undefined };

      const res = await api(realParams);

      tableData.value = res.rows || res.data || [];

      // 非分页模式 total 可以等于返回数据长度
      total.value = pagination ? res.total : tableData.value.length;
    } finally {
      loading.value = false;
    }
  };

  /** 查询 */
  const handleSearch = () => {
    if (pagination) query.pageNum = 1;
    loadData();
  };

  /** 重置查询 */
  const handleReset = (isLoadData: boolean = true) => {
    if (pagination) {
      Object.assign(query, { pageNum: 1, pageSize: 10 }, defaultQuery);
    } else {
      Object.assign(query, defaultQuery);
    }
    isLoadData && loadData();
  };

  /** 分页相关（不需要分页时全部不执行） */
  const handlePageChange = (pageNum: number) => {
    if (!pagination) return;
    query.pageNum = pageNum;
    loadData();
  };

  const handlePageSizeChange = (size: number) => {
    if (!pagination) return;
    query.pageSize = size;
    query.pageNum = 1;
    loadData();
  };

  const refresh = () => loadData();

  if (immediate) onMounted(loadData);

  return {
    query,
    tableData,
    total,
    loading,
    loadData,
    handleSearch,
    handleReset,
    handlePageChange,
    handlePageSizeChange,
    refresh,
    pagination,
  };
}
